﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.ComponentModel;
using System.Drawing;


/*
 * 主要是对DataGridView进行扩展。
 * 使用方法
 *       注册事件方法
        protected void RegisterCellFormatters()
        {
            this.dataGridViewEx1.CellFormatterRegister.RegisterFormatter("Column5",
                new DataGridCellFormatter.CellFormatDelegate(FormatColumn5));
            this.dataGridViewEx1.CellFormatterRegister.RegisterFormatter("Column4",
                new DataGridCellFormatter.CellFormatDelegate(FormatColumn4));
        }
 *   //根据内容改变Column5的文本颜色 例
        internal void FormatColumn5(string columnName, DataGridViewCellFormattingEventArgs e)
        {
            if (e.Value.ToString().Contains("5"))
            {
                e.CellStyle.ForeColor = Color.Green;
            }

            if (e.Value.ToString().Contains("3"))
            {
                e.CellStyle.ForeColor = Color.Red;
            }
        }

        // 根据内容设置自定义按钮列为不可用
        internal void FormatColumn4(string columnName, DataGridViewCellFormattingEventArgs e)
        {
            if (e.Value == null) return;
            if (e.Value.ToString().Contains("2"))
            {
                DataGridViewButtonCellEx cell = 
                    this.dataGridViewEx1.Rows[e.RowIndex].Cells[e.ColumnIndex] as DataGridViewButtonCellEx;
                if (cell != null)
                {
                    cell.Enabled = false;
                }
            }
        }
 *     CellButtonClicked 事件
 *      private void dataGridViewEx1_CellButtonClicked(
            object sender, 
            DataGridViewExs.EventArgsEx.DataGridViewButtonClickEventArgs e)
        {
            MessageBox.Show(string.Format(@" CellButtonClicked的测试 [columnIndex:{0}，rowIndex:{1},value:{2}]", e.ColumnIndex, e.RowIndex, e.Value));
        }
 *         自定义实现的统计行
            DataGridSummaryRowEx summaryRow = this.dataGridViewEx1.CreateSummary();
            summaryRow.Cells[0].Value = "合计";
            summaryRow.Cells[2].Value = 122;
 * 
 * 
 * 
 *
 *      
 */
namespace Liang.UI
{
    /// <summary>
    /// 扩展的DataGridView
    /// </summary>
    public class DataGridViewEx : DataGridView
    {
        /// <summary>
        ///DataGridViewButtonColumnEx中的按钮点击事件，如果没有这个列，
        ///此事件就没有具体作用
        /// </summary>
        [Category("Jonson Design"), Description("按钮点击事件")]
        public event DataGridViewButtonClicked CellButtonClicked;

        [Category("Jonson Design"), Description("列样式文本格式化器")]
        public DataGridCellFormatter CellFormatterRegister
        {
            private set;
            get;
        }

        private string m_FlagColumnName = string.Empty;
        [Category("ut"), Browsable(true), Description("选中标志选中列的一项"), Localizable(true)]
        [DefaultValue(null), Editor(typeof(DataGridViewFlagRowEditor), typeof(System.Drawing.Design.UITypeEditor))]
        public string FlagColumnName
        {
            get
            {
                return m_FlagColumnName;
            }
            set
            {
                m_FlagColumnName = value;
                if (!string.IsNullOrEmpty(m_FlagColumnName))
                    base.SelectionMode = DataGridViewSelectionMode.FullRowSelect;
            }
        }

        public DataGridViewEx()
            : base()
        {
            this.SetStyle(ControlStyles.AllPaintingInWmPaint |
                ControlStyles.UserPaint |
                ControlStyles.OptimizedDoubleBuffer |
                ControlStyles.ResizeRedraw, true);
            //this.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
            this.BackgroundColor = Color.White;
            this.CellFormatterRegister = new DataGridCellFormatter();
            this.RowTemplate.HeaderCell = new DataGridViewRowHeaderCellEx();
            this.ColumnHeadersDefaultCellStyle.Alignment = DataGridViewContentAlignment.MiddleCenter;
            this.BackgroundColor = ColorTranslator.FromHtml("#E9F5FC");
        }

        /// <summary>
        /// checkbox的单元格改变事件
        /// </summary>
        /// <param name="columnIndex"></param>
        /// <param name="rowIndex"></param>
        internal void OnCheckBoxCellCheckedChange(int columnIndex, int rowIndex, bool value)
        {
            bool existsChecked = false, existsNoChecked = false;
            DataGridViewCheckBoxCellEx cellEx;
            foreach (DataGridViewRow row in this.Rows)
            {
                cellEx = row.Cells[columnIndex] as DataGridViewCheckBoxCellEx;
                if (cellEx == null) return;
                existsChecked |= cellEx.Checked;
                existsNoChecked |= !cellEx.Checked;
            }

            DataGridViewCheckBoxColumnHeaderCellEx headerCellEx =
                this.Columns[columnIndex].HeaderCell as DataGridViewCheckBoxColumnHeaderCellEx;

            if (headerCellEx == null) return;

            CheckState oldState = headerCellEx.CheckedAllState;

            if (existsChecked)
                headerCellEx.CheckedAllState = existsNoChecked ? CheckState.Indeterminate : CheckState.Checked;
            else
                headerCellEx.CheckedAllState = CheckState.Unchecked;

            if (oldState != headerCellEx.CheckedAllState)
                this.InvalidateColumn(columnIndex);
        }

        /// <summary>
        /// 全选中/取消全选中
        /// </summary>
        /// <param name="columnIndex"></param>
        /// <param name="isCheckedAll"></param>
        internal void OnCheckAllCheckedChange(int columnIndex, bool isCheckedAll)
        {
            DataGridViewCheckBoxCellEx cellEx;
            foreach (DataGridViewRow row in this.Rows)
            {
                cellEx = row.Cells[columnIndex] as DataGridViewCheckBoxCellEx;
                if (cellEx == null) continue;
                cellEx.Checked = isCheckedAll;
            }
        }

        /// <summary>
        /// 出发DataGridViewColumnEx中的按钮点击事件
        /// </summary>
        /// <param name="columnIndex"></param>
        /// <param name="rowIndex"></param>
        /// <param name="value"></param>
        internal void OnButtonClicked(int columnIndex, int rowIndex, object value)
        {
            this.OnCellButtonClicked(columnIndex, rowIndex, value);
        }

        /// <summary>
        /// 事件触发
        /// </summary>
        /// <param name="columnIndex"></param>
        /// <param name="rowIndex"></param>
        /// <param name="value"></param>
        protected void OnCellButtonClicked(int columnIndex, int rowIndex, object value)
        {
            if (CellButtonClicked != null)
                CellButtonClicked(this, new DataGridViewButtonClickEventArgs(columnIndex, rowIndex, value));
        }


        /// <summary>
        /// 重写单元格格式化事件
        /// </summary>
        /// <param name="e"></param>
        protected override void OnCellFormatting(DataGridViewCellFormattingEventArgs e)
        {
            if (this.Rows[e.RowIndex].Cells[e.ColumnIndex] is DataGridSummaryCellEx)
                return;
            if (this.Rows[e.RowIndex].Cells[e.ColumnIndex] is DataGridViewLinkCellEx)
                return;
            if (this.Rows[e.RowIndex].Cells[e.ColumnIndex] is DataGridViewCheckBoxCellEx)
                return;
            //执行注册的程序
            this.CellFormatterRegister.RunFormatter(this.Columns[e.ColumnIndex].Name, e);
            if ((this.Rows[e.RowIndex].DataBoundItem != null) &&
            (this.Columns[e.ColumnIndex].DataPropertyName.Contains(".")))
            {
                string[] names = this.Columns[e.ColumnIndex].DataPropertyName.Split('.');
                object obj = this.Rows[e.RowIndex].DataBoundItem;
                for (int i = 0; i < names.Length; ++i)
                {
                    try
                    {
                        var result = obj.GetType().GetProperty(names[i]).GetValue(obj, null);
                        obj = result;
                        e.Value = result.ToString();
                    }
                    catch (Exception)
                    {
                        return;
                        throw;
                    }
                }
            }
            base.OnCellFormatting(e);
        }

        DataGridViewCheckBoxCellEx paintCell;
        protected override void OnCellPainting(DataGridViewCellPaintingEventArgs e)
        {
            if (e.ColumnIndex < 0 || e.RowIndex < 0) return;
            if (!this.Columns.Contains(FlagColumnName)) return;
            paintCell = this.Rows[e.RowIndex].Cells[FlagColumnName] as DataGridViewCheckBoxCellEx;
            if (paintCell != null && paintCell.Checked)
            {
                //e.CellStyle.BackColor = e.CellStyle.SelectionBackColor;
                this.Rows[e.RowIndex].Selected = true;
            }

            base.OnCellPainting(e);
        }





        /// <summary>
        /// 在排序之前将统计行去除，使得排序不会根据统计行内容排序
        /// </summary>
        /// <param name="e"></param>
        protected override void OnColumnHeaderMouseClick(DataGridViewCellMouseEventArgs e)
        {
            if (e.Button == System.Windows.Forms.MouseButtons.Left)
                this.RemoveSummaryRow();
            base.OnColumnHeaderMouseClick(e);
            if (e.Button == System.Windows.Forms.MouseButtons.Left)
                this.AppendSummaryRow();
        }


        DataGridSummaryRowEx m_summaryRow = null;

        private void RemoveSummaryRow()
        {
            if (m_summaryRow == null) return;
            if (this.Rows.Contains(m_summaryRow))
                this.Rows.Remove(m_summaryRow);
        }

        private void AppendSummaryRow()
        {
            if (m_summaryRow == null) return;
            this.RemoveSummaryRow();
            int index = this.Rows.Add(m_summaryRow);
            m_summaryRow = this.Rows[index] as DataGridSummaryRowEx;
        }

        /// <summary>
        /// 创建统计行，并且返回统计行对象，以便对单元格进行赋值信息
        /// </summary>
        /// <returns></returns>
        static Color m_summaryBackColor = Color.Linen;
        public DataGridSummaryRowEx CreateSummary()
        {
            if (m_summaryRow == null)
            {
                m_summaryRow = new DataGridSummaryRowEx();

                //添加与column相同的列，单元格是自扩展。
                foreach (DataGridViewColumn col in this.Columns)
                {
                    m_summaryRow.Cells.Add(new DataGridSummaryCellEx());
                }
                m_summaryRow.DefaultCellStyle.BackColor = m_summaryBackColor;
            }
            this.RemoveSummaryRow();
            this.AppendSummaryRow();
            return m_summaryRow;
        }

        /// <summary>
        /// 获取选中项
        /// </summary>
        /// <returns></returns>
        public List<object> GetSelectedItems()
        {
            List<object> ret = new List<object>();

            for (int i = 0; i < Rows.Count; i++)
            {
                if (!(Rows[i].Cells[0] is DataGridViewCheckBoxCellEx))
                {
                    MessageBox.Show("未提供选择列功能");
                    break;
                }

                DataGridViewCheckBoxCellEx cell = Rows[i].Cells[0] as DataGridViewCheckBoxCellEx;

                if (cell.Checked)
                {
                    ret.Add(Rows[i].Cells[1].Value.ToString());
                }
            }

            return ret;
        }

    }
}
